package homework

import (
	"errors"
	"fmt"
	"reflect"
	"strings"
)

var errInvalidEntity = errors.New("invalid entity")

func InsertStmt(entity interface{}) (string, []interface{}, error) {

	if entity == nil {
		return "", nil, errInvalidEntity
	}

	typ := reflect.TypeOf(entity)
	refVal := reflect.ValueOf(entity)

	if typ.Kind() == reflect.Ptr {
		typ = typ.Elem()
		refVal = refVal.Elem()
	}

	if refVal.Kind() != reflect.Struct {
		return "", nil, errInvalidEntity
	}

	numField := typ.NumField()

	if numField == 0 {
		return "", nil, errInvalidEntity
	}

	if refVal.Kind() == reflect.Struct {

		sql := "INSERT INTO " + fmt.Sprintf("`%s`", typ.Name())

		fields := make([]string, 0)
		values := make([]string, 0)
		args := make([]interface{}, 0)
		for i := 0; i < refVal.NumField(); i++ {
			fields = append(fields, fmt.Sprintf("`%s`", typ.Field(i).Name))
			values = append(values, "?")
			args = append(args, refVal.Field(i).Interface())
		}
		sql += fmt.Sprintf("(%s)", strings.Join(fields, ","))
		sql += fmt.Sprintf(" VALUES(%s);", strings.Join(values, ","))

		return sql, args, nil
	}

	// val := reflect.ValueOf(entity)
	// typ := val.Type()
	// 检测 entity 是否符合我们的要求
	// 我们只支持有限的几种输入

	// 使用 strings.Builder 来拼接 字符串
	// bd := strings.Builder{}

	// 构造 INSERT INTO XXX，XXX 是你的表名，这里我们直接用结构体名字

	// 遍历所有的字段，构造出来的是 INSERT INTO XXX(col1, col2, col3)
	// 在这个遍历的过程中，你就可以把参数构造出来
	// 如果你打算支持组合，那么这里你要深入解析每一个组合的结构体
	// 并且层层深入进去

	// 拼接 VALUES，达成 INSERT INTO XXX(col1, col2, col3) VALUES

	// 再一次遍历所有的字段，要拼接成 INSERT INTO XXX(col1, col2, col3) VALUES(?,?,?)
	// 注意，在第一次遍历的时候我们就已经拿到了参数的值，所以这里就是简单拼接 ?,?,?

	// return bd.String(), args, nil
	panic("implement me")
}
